package com.demo.key.load_admob

import com.demo.key.mKey
import com.demo.key.util.Conf0822
import com.demo.key.util.logQwer
import com.google.android.gms.ads.AdListener
import com.google.android.gms.ads.AdLoader
import com.google.android.gms.ads.AdRequest
import com.google.android.gms.ads.LoadAdError
import com.google.android.gms.ads.appopen.AppOpenAd
import com.google.android.gms.ads.interstitial.InterstitialAd
import com.google.android.gms.ads.interstitial.InterstitialAdLoadCallback
import com.google.android.gms.ads.nativead.NativeAdOptions
import com.tencent.mmkv.MMKV
import org.json.JSONObject

object LoadAdmob0822Manager {
    var showingFullAd0822=false
    private val admobDataMap= hashMapOf<String,Admob0822Entity>()
    private val isLoadingAdTagList= arrayListOf<String>()

    fun logic(type:String,loadAgain:Boolean=true){
        if (isLoadingAdTagList.contains(type)){
            logQwer("$type is loading...")
            return
        }
        if (admobDataMap.containsKey(type)){
            val admob0822Entity = admobDataMap[type]
            if (admob0822Entity?.admob!=null) if (!admob0822Entity.ex()){
                logQwer("$type has cache...")
                return
            }else{
                removeAdmobData(type)
            }
        }

        val adListByType = getAdListByType(type)
        if (adListByType.isEmpty()){
            logQwer("$type list no ad data...")
            return
        }
        isLoadingAdTagList.add(type)
        loopLoadAdmob(type,adListByType.iterator(),loadAgain)
    }

    private fun loopLoadAdmob(type: String, ite: Iterator<ConfAd0822Entity>,loadAgain:Boolean=true){
        val next = ite.next()
        startLoadAd(type,next){ success,admobData->
            if (success){
                isLoadingAdTagList.remove(type)
                if (null!=admobData.admob){
                    admobDataMap[type]=admobData
                }
            }else{
                if (ite.hasNext()){
                    loopLoadAdmob(type,ite,loadAgain)
                }else{
                    isLoadingAdTagList.remove(type)
                    if (type==AdmobKeyType.OPEN&&loadAgain){
                        logic(type,loadAgain = false)
                    }
                }
            }
        }
    }

    private fun startLoadAd(type:String,entity:ConfAd0822Entity,loadResult:(success:Boolean,Admob0822Entity)->Unit) {
        logQwer("start load ad,type=$type  id=${entity.id_0822}  type=${entity.type_0822}  sort=${entity.sort_0822}")
        when(entity.type_0822){
            "kaip"-> {
                AppOpenAd.load(
                    mKey,
                    entity.id_0822,
                    AdRequest.Builder().build(),
                    AppOpenAd.APP_OPEN_AD_ORIENTATION_PORTRAIT,
                    object : AppOpenAd.AppOpenAdLoadCallback(){
                        override fun onAdLoaded(p0: AppOpenAd) {
                            super.onAdLoaded(p0)
                            logQwer("load $type ad success")
                            loadResult.invoke(true, Admob0822Entity(System.currentTimeMillis(),p0))
                        }

                        override fun onAdFailedToLoad(p0: LoadAdError) {
                            super.onAdFailedToLoad(p0)
                            logQwer("load $type ad fail,reason:${p0.message}")
                            loadResult.invoke(false,Admob0822Entity())
                        }
                    }
                )
            }
            "chap"->{
                InterstitialAd.load(
                    mKey,
                    entity.id_0822,
                    AdRequest.Builder().build(),
                    object : InterstitialAdLoadCallback(){
                        override fun onAdFailedToLoad(p0: LoadAdError) {
                            logQwer("load $type ad fail,reason:${p0.message}")
                            loadResult.invoke(false,Admob0822Entity())
                        }

                        override fun onAdLoaded(p0: InterstitialAd) {
                            logQwer("load $type ad success")
                            loadResult.invoke(true, Admob0822Entity(System.currentTimeMillis(),p0))
                        }
                    }
                )
            }
            "yuans"->{
                AdLoader.Builder(
                    mKey,
                    entity.id_0822
                ).forNativeAd {
                    logQwer("load $type ad success")
                    loadResult.invoke(true, Admob0822Entity(System.currentTimeMillis(),it))
                }
                    .withAdListener(object : AdListener(){
                        override fun onAdFailedToLoad(p0: LoadAdError) {
                            super.onAdFailedToLoad(p0)
                            logQwer("load $type ad fail,reason:${p0.message}")
                            loadResult.invoke(false,Admob0822Entity())
                        }
                    })
                    .withNativeAdOptions(
                        NativeAdOptions.Builder()
                            .setAdChoicesPlacement(
                                NativeAdOptions.ADCHOICES_TOP_RIGHT
                            )
                            .build()
                    )
                    .build()
                    .loadAd(AdRequest.Builder().build())
            }
        }
    }

    private fun getAdListByType(type: String): List<ConfAd0822Entity> {
        val mmkvAdJson = getMMKVAdJson()
        val list= arrayListOf<ConfAd0822Entity>()
        try {
            val jsonArray = JSONObject(mmkvAdJson).getJSONArray(type)
            for (index in 0 until jsonArray.length()){
                val jsonObject = jsonArray.getJSONObject(index)
                val conf0816AdEn = ConfAd0822Entity(
                    jsonObject.optString("key_source"),
                    jsonObject.optString("key_id"),
                    jsonObject.optString("key_type"),
                    jsonObject.optInt("key_sort"),
                )
                list.add(conf0816AdEn)
            }
        }catch (e:Exception){}
        return list.filter { it.source_0822 == "admob" }.sortedByDescending { it.sort_0822 }
    }

    private fun getMMKVAdJson():String{
        val ad_json = MMKV.defaultMMKV().decodeString("ad_json")
        return if (ad_json.isNullOrEmpty()) {
            Conf0822.AD_CONF0822
        } else {
            ad_json
        }
    }

    fun getAdDataByType(type: String) = admobDataMap[type]

    fun removeAdmobData(type: String){
        admobDataMap.remove(type)
    }
}